iT邦幫忙

第 12 屆 iThome 鐵人賽

DAY 22
2

前言
2020 秋天,我將用 30 天的時間,來嘗試回答和網路前端開發相關的 30 個問題。30 天無法一網打盡浩瀚的前端知識,有些問題可能對有些讀者來說相對簡單,不過期待這趟旅程,能幫助自己、也幫助讀者打開不同的知識大門。有興趣的話,跟著我一起探索吧!

WebSocket 的誕生

今天要來聊聊一個不同於 HTTP 的連線方式:WebSocket

如果還記得我們在這篇文章當中提過的 OSI model,在 application layer 這一層當中有許多的協議,譬如 HTTP, FTP, TELNET 等等,其中也包含了 WebSocket

最初在只有 HTTP 的時候,client 可以透過 HTTP request 來向 server 請求資訊,當 server 回傳 HTTP response 之後,連線就會中斷。不過如果今天 server 有資訊想要讓 client 端知道,基本上就只能等下次 client 發出請求的時候,server 再把資訊傳給 client。

如果今天資訊的更新頻率很高,但 client 也不確定新的資訊什麼時候會出現的情況下,就會採取「輪詢」的方式與 server 建立連線。輪詢的意思就是,client 定時地發出 HTTP request,讓 client 能夠較為及時的收到最新資訊。這樣的做法看似可以簡單地解決問題,但實際上在效能的表現上沒有很好,因為每一次的請求都會佔用資源,而其實 client 不知道哪一次的請求才會真正的拿到最新資訊。

最常見的場景,就是聊天室的應用。client 需要一直更新來自 server 的最新資訊。

為了更有效的解決這個問題,WebSocket 在 2008 年左右因而誕生。

WebSocket 的優點

HTTP 最大的差別是,WebScoket 在建立連線之後,可以實現 client 與 server 的雙向溝通機制,也就是說,雙方可以即時的交換資訊,不用再等待 client 發出請求,或使用佔用資源的輪詢方式來實現。

另一方面,在建立連線之後就會持續保持著連線狀態,所以每次通訊時所發出的 message,就可以省略掉 headers 當中一些關於連線狀態的資訊,也就因此提高了效率。

HTTP 相同的是,WebSocket 也是使用 TCP 連線。WebSocketHTTPHTTPS 有兼容性,默認的 port 也是為 80 和 443,並透過同樣的 HTTP 3-way handshake 建立連線。

若要進行像是 HTTPS 當中的 SSL/TLS 的加密安全傳輸,也有 WebSocket Secure 協議可以使用。

WebSocket 的使用

WebSocket 在使用上其實不難。MDN 上有關於 WebSocket API (client 端) 的範例。這裡我們來簡單建立一下連線:

// Create WebSocket connection.
const socket = new WebSocket("wss://echo.websocket.org");

// Connection opened
socket.addEventListener('open', function (event) {
    console.log('Open connection')
    socket.send('Hello Server!');
});

// Listen for messages
socket.addEventListener('message', function (event) {
    console.log(`Message from server: ${event.data}`);
});

如果把上面這段程式碼貼到 DevTool 的 console 當中,就可以看到其連線運作。內容其實相當簡單,首先建立 WebSocket 連線實例,接著,就可以監聽各種 events,像是

  • open (連線開啟)
  • close (連線關閉)
  • error (連線錯誤)
  • message (連線訊息)

之後,再根據不同的 events 做出不同的對應方式,譬如在畫面上呈現連線訊息等。除了監聽事件之外,也可以透過 socket.send() 來送出資訊,以及 send.close() 來關閉連線。

MDN 上介紹的 WebSocket API 其實就可以幫助我們快速建立 WebSocket 連線。不過如果我們想要在自己的專案當中進行更複雜的操作,也可以找到很完整的套件來幫助我們,譬如 socket.io,可以同時用在 client 端與 server 端。

End

有了 WebSocket 讓我們的應用程式可以和使用者有更多的互動,除了「聊天室」的應用之外,還有其他的應用場景像是「訊息推播」、「即時訊息更新」、「共同編輯」等等,用提相當廣泛。有機會的話,也試著做一個使用 WebSocket 的應用程式吧!

Ref


TD
Be curious as astronomer, think as physicist, hack as engineer, fight as baseball player

More about me

"Life is like riding a bicycle. To keep your balance, you must keep moving."


上一篇
HTTP, HTTPS, HTTP2
下一篇
Debounce & Throttling
系列文
前端開發 30 個問題31
圖片
  直播研討會
圖片
{{ item.channelVendor }} {{ item.webinarstarted }} |
{{ formatDate(item.duration) }}
直播中

尚未有邦友留言

立即登入留言